﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Media;
using MineBoxRelease.Model;
using NSoup.Nodes;
using NSoup.Select;

namespace MineBoxRelease.Core
{
    internal class ZFHtmlParser
    {
        private static Color[] CourseColors =
        {
            Color.FromRgb(0x76, 0xAA, 0x38),
            Color.FromRgb(0x42, 0x99, 0xBE),
            Color.FromRgb(0xD0, 0xA1, 0x4B),
            Color.FromRgb(0x69, 0x83, 0xC1),
            Color.FromRgb(0xCC, 0x76, 0x77),
            Color.FromRgb(0x48, 0x92, 0x6A),
            /*Color.FromRgb(0xCC, 0xCC, 0x36),*/
        };

        private Document doc;

        public ZFHtmlParser(string html)
        {
            doc = NSoup.NSoupClient.Parse(html);
        }

        #region 解析课程表

        //课程表解析
        //改进：兼容体育课等个别格式课程的解析
        public CourseSet GetSchedule()
        {
            CourseSet courseSet = new CourseSet();
            Elements trs = doc.GetElementById("Table1").GetElementsByTag("tr");
            //删除“时间”、“早晨”行
            trs.Remove(trs[0]);
            trs.Remove(trs[0]);
            for (int row = 0; row < trs.Count; row += 2)
            {
                Elements tds = trs[row].GetElementsByTag("td");
                //删除“上午”列
                if (row % 4 == 0) tds.Remove(tds[0]);
                //删除“第1节”列
                tds.Remove(tds[0]);
                for (int col = 0; col < tds.Count; col++)
                {
                    string tdStr = tds[col].Html().Trim();
                    //过滤空白格子
                    if (tdStr.Equals("&nbsp;") || !tdStr.Any()) continue;
                    string[] separatorr = { "<br /><br />", "<br /> <br />" };
                    string[] courses = tds[col].Html().Split(separatorr, StringSplitOptions.RemoveEmptyEntries);
                    foreach (string courseStr in courses)
                    {
                        if (courseStr.StartsWith("<font")) continue;
                        {
                            Course course = ParseToCourse(courseStr, row, col);
                            Debug.WriteLine(course.ToString());
                            courseSet.AddNotRepeat(course);
                        }
                    }
                }
            }
            return courseSet;
        }

        /// <summary>
        /// 将字符串解析为Course对象
        /// </summary>
        /// <param name="courseStr">形如：汇编语言程序设计<br>周一第1,2节{第15-15周|单周}<br>蔡沂<br>B5-504</param>
        /// <param name="row">行（第几节）</param>
        /// <param name="col">列（星期几）</param>
        /// <returns></returns>
        private Course ParseToCourse(String courseStr, int row, int col)
        {
            courseStr = courseStr.Trim();
            string[] separator = { "<br />" };
            string[] courseInfos = courseStr.Split(separator, StringSplitOptions.None);

            //提取标题、教师名称
            string name = courseInfos[0].Trim();
            string teacherName = courseInfos[2].Trim();
            if (teacherName.IndexOf('(') > 0)
                teacherName = teacherName.Substring(0, teacherName.IndexOf('('));

            //提取上课时段、上课地点
            string coursePeriodStr = courseInfos[1].Trim();
            string site = courseInfos[3].Trim();
            CoursePeriod period = ParseToCoursePeriod(coursePeriodStr, site, row, col);

            Course course = new Course();
            course.CourseColor = CourseColors[(row + col) % CourseColors.Count()];
            course.Name = name;
            course.TeacherName = teacherName;
            course.Periods.Add(period);
            return course;
        }

        /// <summary>
        /// 将字符串解析为CoursePeriod对象
        /// </summary>
        /// <param name="coursePeriodStr">形如：周一第1,2节{第15-15周|单周} 或 {第2-17周|2节/周}</param>
        /// <param name="row">行（第几节）</param>
        /// <param name="col">列（星期几）</param>
        /// <returns></returns>
        private CoursePeriod ParseToCoursePeriod(String coursePeriodStr, string site, int row, int col)
        {
            int startWeek = 0;
            int endWeek = 0;
            WeekType weekType = WeekType.All;

            //对于 {第2-17周|2节/周} 的处理
            if (coursePeriodStr.StartsWith("{"))
            {
                string[] separator = { "{第", "-", "周" };
                string[] infoStrs = coursePeriodStr.Split(separator, StringSplitOptions.RemoveEmptyEntries);
                startWeek = int.Parse(infoStrs[0]);
                endWeek = int.Parse(infoStrs[1]);
            }
            //对于 周一第1,2节{第15-15周|单周} 的处理
            else
            {
                string[] separator = { "{第", "-", "周|", "周}" };
                string[] infoStrs = coursePeriodStr.Split(separator, StringSplitOptions.RemoveEmptyEntries);
                startWeek = int.Parse(infoStrs[1]);
                endWeek = int.Parse(infoStrs[2]);
                if (infoStrs.Count() > 3)
                {
                    switch (infoStrs[3])
                    {
                        case "单":
                            ;
                            weekType = WeekType.Odd;
                            break;
                        case "双":
                            weekType = WeekType.Even;
                            break;
                    }
                }
            }


            CoursePeriod period = new CoursePeriod();
            period.Day = col;
            period.Period = row / 2;
            period.Site = site;
            period.StartWeek = startWeek;
            period.EndWeek = endWeek;
            period.WeekType = weekType;
            return period;
        }

        #endregion

        #region 解析登陆结果信息

        public string GetLoginResult()
        {
            Elements forms = doc.GetElementsByTag("form");
            if (forms == null || forms.Count == 0) return "未知错误";
            Element form = forms[0];
            if (form.Id != "form1") return null;
            Element script = form.GetElementsByTag("script")[0];
            if (script == null) return null;
            string[] separater = { "alert('", "');" };
            string info = script.Html().Split(separater, StringSplitOptions.RemoveEmptyEntries)[0];
            return info;
        }

        #endregion
    }
}
